/*
 * Copyright (C) 2015-2018 Alibaba Group Holding Limited
 */

#include <k_api.h>

#include <platform/wm_fwup.h>
#include "app_main.h"

#define OTA_STATUS_IDLE  0
#define OTA_STATUS_START 1
#define OTA_STATUS_STOP  2

extern int   dm_ota_get_ota_handle(void **handle);
unsigned int session_id = 0;
static int   ota_status = OTA_STATUS_IDLE;

static int app_smartliving_fota_failed_rpt(void)
{
    void *ota_handle = NULL;
    int   res        = 0;
    /* Get Ota Handle */
    res = dm_ota_get_ota_handle(&ota_handle);
    if (res != SUCCESS_RETURN) {
        LOGE(TAG, "dm_ota_get_ota_handle failed %d", res);
        return res;
    }

    res = IOT_OTA_ReportProgress(ota_handle, IOT_OTAP_CHECK_FALIED, NULL);
    if (res != 0) {
        LOGE(TAG, "IOT_OTA_ReportProgress failed %s!", res);
    }

    return res;
}

static void user_ota_event_cb(uint32_t event_id, const void *param, void *context)
{
    LOGD(TAG, "enter %s, event_id %d", __FUNCTION__, event_id);
    if (EVENT_USER_OTA_VERIFY_FAIL == event_id) {
        app_smartliving_fota_failed_rpt();
    }
}

tls_fwup_status_callback fw_finish_callback(int err)
{
    tls_fwup_exit(session_id);
    if (err != 0) {
        LOGE(TAG, "fota fw check failed [%d]!", err);
        event_publish(EVENT_USER_OTA_VERIFY_FAIL, NULL);
    } else {
        event_publish(EVENT_USER_OTA_VERIFY_SUCCESS, NULL);
    }
    ota_status = OTA_STATUS_STOP;
}

void HAL_Firmware_Persistence_Start(uint32_t file_size)
{
    if (ota_status == OTA_STATUS_START) {
        LOGD(TAG, "OTA has already started!");
        return;
    }

    LOGD(TAG, "%s, file_size %d", __FUNCTION__, file_size);
    session_id = tls_fwup_enter(TLS_FWUP_IMAGE_SRC_WEB, file_size);

    tls_fwup_reg_status_callback((tls_fwup_status_callback)fw_finish_callback);
    event_subscribe(EVENT_USER_OTA_VERIFY_SUCCESS, user_ota_event_cb, NULL);
    event_subscribe(EVENT_USER_OTA_VERIFY_FAIL, user_ota_event_cb, NULL);

    ktask_t *h   = NULL;
    int      ret = 0;
    h            = krhino_task_find("breeze_rx");
    if (h) {
        krhino_task_dyn_del(h);
        aos_msleep(500);
    }
    h = krhino_task_find("hci_rx_task");
    if (h) {
        krhino_task_del(h);
        aos_msleep(500);
    }
    h = krhino_task_find("BTC");
    if (h) {
        krhino_task_del(h);
        aos_msleep(500);
    }
    h = krhino_task_find("ecc task");
    if (h) {
        krhino_task_del(h);
        aos_msleep(500);
    }
    h = krhino_task_find("hci rx");
    if (h) {
        krhino_task_del(h);
        aos_msleep(500);
    }
    h = krhino_task_find("hci tx");
    if (h) {
        krhino_task_del(h);
        aos_msleep(500);
    }

    ota_status = OTA_STATUS_START;
}

int HAL_Firmware_Persistence_Stop(void)
{
    LOGD(TAG, "%s: ota download finished, please wait few seconds for data copying ...", __FUNCTION__);
    tls_fwup_exit(session_id);
    aos_reboot();

    return SUCCESS_RETURN;
}

int HAL_Firmware_Persistence_Write(char *buffer, uint32_t length)
{
    int ret = -1;
    if (ota_status != OTA_STATUS_START) {
        LOGE(TAG, "OTA in wrong state!");
        return ret;
    }
    ret = tls_fwup_request_sync(session_id, buffer, length);

    return ret;
}